package ro.licenta.utilities.services;

import java.util.Calendar;
import java.util.Date;
import java.util.Timer;
import java.util.TimerTask;

import ro.licenta.main.MainActivity;
import ro.licenta.tama.Tama;
import ro.licenta.utilities.utils.PreferencesUtils;
import ro.licenta.utilities.utils.StaticUtils;
import android.app.Notification;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.Binder;
import android.os.IBinder;
import android.support.v4.app.NotificationCompat;

import com.example.test.R;

public class MyService extends Service {

	private final IBinder mBinder = new MyBinder();
	private Timer updateInfo;
	private boolean dead;
	private Tama tTama;
	private PreferencesUtils mPrefs;
	private Calendar currentCalendar, currentCalendarAge;

	@Override
	public void onCreate() {
		tTama = Tama.getInstance();
		mPrefs = new PreferencesUtils(getApplicationContext());

		if (tTama.isThesys()) {
			currentCalendar = Calendar.getInstance();
			currentCalendar.add(Calendar.MINUTE, tTama.getUpdateService());

			currentCalendarAge = Calendar.getInstance();
			currentCalendarAge.add(Calendar.MINUTE, tTama.getLifeCycle());
		} else {

			currentCalendar = Calendar.getInstance();
			currentCalendar.add(Calendar.HOUR, tTama.getUpdateService());

			currentCalendarAge = Calendar.getInstance();
			currentCalendarAge.add(Calendar.HOUR, tTama.getLifeCycle());
		}
		System.out.println("OnCreateService");
		CancelNotification(this, StaticUtils.notifyIdHp);
		CancelNotification(this, StaticUtils.notifyIdFull);
		CancelNotification(this, StaticUtils.notifyIdFun);
		CancelNotification(this, StaticUtils.notifyIdEne);
		CancelNotification(this, StaticUtils.notifyIdDead);
		updateNotif();

	}

	@Override
	public int onStartCommand(Intent intent, int flags, int startId) {
		dead = tTama.isDead();
		if (!dead) {
			startupdateInfo();
		} else {
			stopSelf();
		}
		return Service.START_STICKY;
	}

	@Override
	public IBinder onBind(Intent arg0) {
		return mBinder;
	}

	public class MyBinder extends Binder {
		public MyService getService() {
			return MyService.this;
		}
	}

	@Override
	public void onDestroy() {
		stopupdateInfo();
		if (tTama.getAge() == StaticUtils.ageDead) {
			tTama.setEne(0);
			tTama.setHp(0);
			tTama.setFull(0);
			tTama.setFun(0);
		}
		CancelNotification(this, StaticUtils.notifyIdHp);
		CancelNotification(this, StaticUtils.notifyIdFull);
		CancelNotification(this, StaticUtils.notifyIdFun);
		CancelNotification(this, StaticUtils.notifyIdEne);
		System.out.println("OnDestroyService");
	}

	private void updateUi() {
		Intent broadcastNotifIntent = new Intent();
		broadcastNotifIntent.setAction(StaticUtils.ACTION_RESP);
		broadcastNotifIntent.addCategory(Intent.CATEGORY_DEFAULT);
		sendBroadcast(broadcastNotifIntent);

	}

	private void updateNotif() {

		tTama = Tama.getInstance();
		if (tTama.isDead()) {
			showNotification("Dead", "I died :( !", StaticUtils.notifyIdDead,
					tTama.isSound());
			stopSelf();
		} else {

			if ((tTama.getHp() > 50) && (tTama.getHp() <= 75)) {
				showNotification("Health",
						"A bit under the weather, do something with me.",
						StaticUtils.notifyIdHp, false);
			}
			if ((tTama.getEne() > 50) && (tTama.getEne() <= 75)) {
				showNotification("Energy", "A tad tired, can I go to sleep?",
						StaticUtils.notifyIdEne, false);
			}
			if ((tTama.getFull() > 50) && (tTama.getFull() <= 75)) {
				showNotification("Fullness", "A bit hungry, can you feed me?",
						StaticUtils.notifyIdFull, false);
			}
			if ((tTama.getFun() > 50) && (tTama.getFun() <= 75)) {
				showNotification("Fun", "A bit bored, can you play with me?",
						StaticUtils.notifyIdFun, false);
			}

			if ((tTama.getHp() > 25) && (tTama.getHp() <= 50)) {
				showNotification(
						"Health",
						"I'm feeling under the weather, please do something with me.",
						StaticUtils.notifyIdHp, false);
			}
			if ((tTama.getEne() > 25) && (tTama.getEne() <= 50)) {
				showNotification("Energy", "Tired, can I go to sleep, please?",
						StaticUtils.notifyIdEne, false);
			}
			if ((tTama.getFull() > 25) && (tTama.getFull() <= 50)) {
				showNotification("Fullness",
						"Hungry, can you feed me, please?",
						StaticUtils.notifyIdFull, false);
			}
			if ((tTama.getFun() > 25) && (tTama.getFun() <= 50)) {
				showNotification("Fun", "Bored, can you play with me, please?",
						StaticUtils.notifyIdFun, false);
			}

		}
	}

	private void showNotification(CharSequence textTitle,
			CharSequence textMessage, int notifyId, boolean sound) {

		NotificationManager nm = (NotificationManager) this
				.getSystemService(Context.NOTIFICATION_SERVICE);

		PendingIntent intent = PendingIntent.getActivity(this, 0, new Intent(
				this, MainActivity.class), 0);

		NotificationCompat.Builder builder = new NotificationCompat.Builder(
				this);
		builder.setContentTitle(textTitle).setContentText(textMessage)
				.setContentIntent(intent);

		if (notifyId == StaticUtils.notifyIdDead)
			builder.setSmallIcon(R.drawable.android);

		if (notifyId == StaticUtils.notifyIdHp)
			builder.setSmallIcon(R.drawable.android);

		if (notifyId == StaticUtils.notifyIdFull)
			builder.setSmallIcon(R.drawable.food_pizza);

		if (notifyId == StaticUtils.notifyIdFun)
			builder.setSmallIcon(R.drawable.fun_basketball);

		if (notifyId == StaticUtils.notifyIdEne)
			builder.setSmallIcon(R.drawable.bed_bear);

		if (sound)
			builder.setSound(GetAlarmUri());

		Notification notif = builder.build();

		notif.flags = Notification.FLAG_ONGOING_EVENT
				| Notification.FLAG_NO_CLEAR
				| PendingIntent.FLAG_UPDATE_CURRENT;
		if (dead) {
			notif.flags = Notification.FLAG_AUTO_CANCEL;
		}
		nm.notify(notifyId, notif);
	}

	private Uri GetAlarmUri() {
		Uri alert = Uri.parse("android.resource://" + getPackageName() + "/"
				+ R.raw.sadt);
		return alert;
	}

	private static void CancelNotification(Context ctx, int notifyId) {
		String ns = Context.NOTIFICATION_SERVICE;
		NotificationManager nMgr = (NotificationManager) ctx
				.getSystemService(ns);
		nMgr.cancel(notifyId);
	}

	private void modifyStats(int valFun, int valEne, int valFull) {
		Calendar referenceCalendar = Calendar.getInstance();
		tTama = Tama.getInstance();

		if (tTama.isThesys()) {
			if (referenceCalendar.get(Calendar.MINUTE) == currentCalendar
					.get(Calendar.MINUTE)) {
				tTama.modifyEne(valEne);
				mPrefs.setEne(tTama.getEne());
				tTama.modifyFun(valFun);
				mPrefs.setFun(tTama.getFun());
				tTama.modifyFull(valFull);
				mPrefs.setFull(tTama.getFull());
				if ((tTama.getEne() == 0) || (tTama.getFull() == 0)) {
					tTama.modifyHp(-15);
				} else {
					tTama.modifyHp();
					mPrefs.setHp(tTama.getHp());
				}
				currentCalendar.add(Calendar.MINUTE, tTama.getUpdateService());
			}

			if (referenceCalendar.get(Calendar.MINUTE) == currentCalendarAge
					.get(Calendar.MINUTE)) {
				int futureAge = tTama.getAge() + 1;
				tTama.setAge(futureAge);
				mPrefs.setAge(futureAge);
				currentCalendarAge.add(Calendar.MINUTE, tTama.getLifeCycle());
			}
		} else {
			if (referenceCalendar.get(Calendar.HOUR) == currentCalendar
					.get(Calendar.HOUR)) {
				tTama.modifyEne(valEne);
				mPrefs.setEne(tTama.getEne());
				tTama.modifyFun(valFun);
				mPrefs.setFun(tTama.getFun());
				tTama.modifyFull(valFull);
				mPrefs.setFull(tTama.getFull());
				if ((tTama.getEne() == 0) || (tTama.getFull() == 0)) {
					tTama.modifyHp(-15);
				} else {
					tTama.modifyHp();
					mPrefs.setHp(tTama.getHp());
				}
				currentCalendar.add(Calendar.MINUTE, 1);
			}

			if (referenceCalendar.get(Calendar.HOUR) == currentCalendarAge
					.get(Calendar.HOUR)) {
				int futureAge = tTama.getAge() + 1;
				if (futureAge == 2) {
					currentCalendarAge.add(Calendar.HOUR, 10);
				}
				if (futureAge == 3) {
					currentCalendarAge.add(Calendar.HOUR, 5);
				}
				tTama.setAge(futureAge);
				mPrefs.setAge(futureAge);

			}
		}

	}

	public void startupdateInfo() {
		long diffInMillis = 0;
		long repeatRate = 0;
		updateInfo = new Timer("UpdateInfo");
		tTama = Tama.getInstance();
		if (tTama.isThesys()) {
			Calendar currentTime = Calendar.getInstance();
			Calendar futureTime = Calendar.getInstance();
			futureTime.set(Calendar.DATE, currentTime.get(Calendar.DATE));
			futureTime.set(Calendar.HOUR, currentTime.get(Calendar.HOUR));
			futureTime.set(Calendar.MINUTE,
					currentTime.get(Calendar.MINUTE) + 1);
			futureTime.set(Calendar.SECOND, 1);
			Date futureDate = futureTime.getTime();
			Date currentDate = currentTime.getTime();
			diffInMillis = futureDate.getTime() - currentDate.getTime();
			repeatRate = tTama.getUpdateService() * 60 * 1000;
		} else {
			Calendar currentTime = Calendar.getInstance();
			Calendar futureTime = Calendar.getInstance();
			futureTime.set(Calendar.DATE, currentTime.get(Calendar.DATE));
			futureTime.set(Calendar.HOUR, currentTime.get(Calendar.HOUR) + 1);
			futureTime.set(Calendar.MINUTE, 5);
			futureTime.set(Calendar.SECOND, 1);
			Date futureDate = futureTime.getTime();
			Date currentDate = currentTime.getTime();
			diffInMillis = futureDate.getTime() - currentDate.getTime();
			repeatRate = tTama.getUpdateService() * 60 * 60 * 1000;

		}
		System.out.println("------------------------------------------------------------------");
		System.out.println("DiffInMillis = " + diffInMillis);
		System.out.println("repeatRate = " + repeatRate);
		System.out.println("------------------------------------------------------------------");
		
		updateInfo.scheduleAtFixedRate(new updateInfo(), diffInMillis,
				repeatRate);
	}

	public void stopupdateInfo() {
		updateInfo.cancel();
	}

	private class updateInfo extends TimerTask {

		@Override
		public void run() {
			if (!tTama.isSleeping())
				modifyStats(-10, -10, -10);
			else
				modifyStats(-5, 10, -5);
			updateNotif();
			updateUi();
		}

	}
}
